home *** CD-ROM | disk | FTP | other *** search
/ Aminet 52 / Aminet 52 (2002)(GTI - Schatztruhe)[!][Dec 2002].iso / Aminet / util / moni / Scout-src.lha / source / objects / scout_commands.c < prev    next >
Encoding:
C/C++ Source or Header  |  2002-09-17  |  15.8 KB  |  451 lines

  1. /**
  2.  * Scout - The Amiga System Monitor
  3.  *
  4.  *------------------------------------------------------------------
  5.  *
  6.  * This program is free software; you can redistribute it and/or modify
  7.  * it under the terms of the GNU General Public License as published by
  8.  * the Free Software Foundation; either version 2 of the License, or
  9.  * any later version.
  10.  *
  11.  * This program is distributed in the hope that it will be useful,
  12.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.  * GNU General Public License for more details.
  15.  *
  16.  * You should have received a copy of the GNU General Public License
  17.  * along with this program; if not, write to the Free Software
  18.  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  19.  *
  20.  * You must not use this source code to gain profit of any kind!
  21.  *
  22.  *------------------------------------------------------------------
  23.  *
  24.  * @author Andreas Gelhausen
  25.  * @author Richard Körber <rkoerber@gmx.de>
  26.  */
  27.  
  28. #include "system_headers.h"
  29.  
  30. struct CommandsCallbackUserData {
  31.     APTR ud_Tree;
  32.     ULONG ud_Count;
  33. };
  34.  
  35. static __asm __saveds LONG comtree_confunc(register __a2 Object *obj, register __a1 struct MUIP_NListtree_ConstructMessage *msg, register __a0 struct Hook *hook)
  36. {
  37.     return AllocListEntry(msg->MemPool, msg->UserData, sizeof(struct CommandEntry));
  38. }
  39.  
  40. MakeHook(comtree_conhook, comtree_confunc);
  41.  
  42. static __asm __saveds LONG comtree_desfunc(register __a2 Object *obj, register __a1 struct MUIP_NListtree_ConstructMessage *msg, register __a0 struct Hook *hook)
  43. {
  44.     FreeListEntry(msg->MemPool, &msg->UserData);
  45.  
  46.     return 0;
  47. }
  48.  
  49. MakeHook(comtree_deshook, comtree_desfunc);
  50.  
  51. static __asm __saveds LONG comtree_dspfunc(register __a2 Object *obj, register __a1 struct MUIP_NListtree_DisplayMessage *msg, register __a0 struct Hook *hook)
  52. {
  53.     static UBYTE *empty = "\0";
  54.  
  55.     if (msg->TreeNode) {
  56.         struct CommandEntry *ce = msg->TreeNode->tn_User;
  57.  
  58.         if (stricmp(ce->ce_Type, "SEG_SINGLE") == 0 || stricmp(ce->ce_Type, "SEG_LIST") == 0) {
  59.             msg->Array[0] = ce->ce_Address;
  60.             msg->Array[1] = ce->ce_Name;
  61.             msg->Array[2] = ce->ce_UseCount;
  62.             msg->Array[3] = ce->ce_SegmentNumStr;
  63.             msg->Array[4] = ce->ce_Lower;
  64.             msg->Array[5] = ce->ce_Upper;
  65.             msg->Array[6] = ce->ce_Size;
  66.         } else {
  67.             msg->Array[0] = empty;
  68.             msg->Array[1] = empty;
  69.             msg->Array[2] = empty;
  70.             msg->Array[3] = ce->ce_SegmentNumStr;
  71.             msg->Array[4] = ce->ce_Lower;
  72.             msg->Array[5] = ce->ce_Upper;
  73.             msg->Array[6] = ce->ce_Size;
  74.         }
  75.     } else {
  76.         msg->Array[0] = "Address";
  77.         msg->Array[1] = "Name";
  78.         msg->Array[2] = "UseCount";
  79.         msg->Array[3] = "Segment";
  80.         msg->Array[4] = "Lower";
  81.         msg->Array[5] = "Upper";
  82.         msg->Array[6] = "Size";
  83.         msg->Preparse[0] = MUIX_B;
  84.         msg->Preparse[1] = MUIX_B;
  85.         msg->Preparse[2] = MUIX_B;
  86.         msg->Preparse[3] = MUIX_B;
  87.         msg->Preparse[4] = MUIX_B MUIX_C;
  88.         msg->Preparse[5] = MUIX_B MUIX_C;
  89.         msg->Preparse[6] = MUIX_B;
  90.     }
  91.  
  92.     return 0;
  93. }
  94.  
  95. MakeHook(comtree_dsphook, comtree_dspfunc);
  96.  
  97. static __asm __saveds LONG comtree_cmpfunc(register __a2 Object *obj, register __a1 struct MUIP_NListtree_CompareMessage *msg, register __a0 struct Hook *hook)
  98. {
  99.     return stricmp(msg->TreeNode1->tn_Name, msg->TreeNode2->tn_Name);
  100. }
  101.  
  102. MakeHook(comtree_cmphook, comtree_cmpfunc);
  103.  
  104. static __asm __saveds LONG comtree_findfunc(register __a2 Object *obj, register __a1 struct MUIP_NListtree_FindUserDataMessage *msg, register __a0 struct Hook *hook)
  105. {
  106.     struct CommandEntry *ce;
  107.  
  108.     ce = (struct CommandEntry *)msg->UserData;
  109.  
  110.     if (ce) {
  111.         return strcmp((UBYTE *)msg->User, ce->ce_Name);
  112.     } else {
  113.         return ~0;
  114.     }
  115. }
  116.  
  117. MakeHook(comtree_findhook, comtree_findfunc);
  118.  
  119. UBYTE *GetUCType( LONG uc )
  120. {
  121.     static LONG uctype[] = { CMD_SYSTEM, CMD_INTERNAL, CMD_DISABLED, 0 };
  122.     static UBYTE *uctypetext[] = { "SYSTEM", "INTERNAL", "DISABLED", NULL };
  123.  
  124.     int i = 0;
  125.  
  126.     while (uctype[i]) {
  127.         if (uc == uctype[i]) {
  128.             return (uctypetext[i]);
  129.         }
  130.         i++;
  131.      }
  132.  
  133.      return NULL;
  134. }
  135.  
  136. static void ReceiveList( void (* callback)( struct CommandEntry *ce, void *userData ),
  137.                          void *userData )
  138. {
  139.     struct CommandEntry *ce;
  140.  
  141.     if (ce = tbAllocVecPooled(globalPool, sizeof(struct CommandEntry))) {
  142.         if (SendDaemon("GetComList")) {
  143.             while (ReceiveDecodedEntry((UBYTE *)ce, sizeof(struct CommandEntry))) {
  144.                 callback(ce, userData);
  145.             }
  146.         }
  147.  
  148.         tbFreeVecPooled(globalPool, ce);
  149.     }
  150. }
  151.  
  152. static void IterateList( void (* callback)( struct CommandEntry *ce, void *userData ),
  153.                          void *userData )
  154. {
  155.     struct MinList tmplist;
  156.     struct CommandEntry *ce, *_ce;
  157.     struct Segment *seg;
  158.  
  159.     NewList((struct List *)&tmplist);
  160.  
  161.     Forbid();
  162.  
  163.     seg = (struct Segment *)BADDR(DEVINFO->di_NetHand);
  164.     while (seg) {
  165.         if (ce = AllocVec(sizeof(struct CommandEntry), MEMF_PUBLIC)) {
  166.             UBYTE *tmp;
  167.  
  168.             ce->ce_Addr = seg;
  169.             _snprintf(ce->ce_Address, sizeof(ce->ce_Address), "$%08lx", seg);
  170.             b2cstrn(MKBADDR(seg->seg_Name), ce->ce_Name, sizeof(ce->ce_Name));
  171.  
  172.             if (tmp = GetUCType(seg->seg_UC)) {
  173.                 stccpy(ce->ce_UseCount, tmp, sizeof(ce->ce_UseCount));
  174.  
  175.                 stccpy(ce->ce_Lower, MUIX_C "---", sizeof(ce->ce_Lower));
  176.                 stccpy(ce->ce_Upper, MUIX_C "---", sizeof(ce->ce_Upper));
  177.                 stccpy(ce->ce_Size, MUIX_R "---", sizeof(ce->ce_Size));
  178.  
  179.                 ce->ce_SegmentNum = -1;
  180.                 stccpy(ce->ce_SegmentNumStr, "---", sizeof(ce->ce_SegmentNumStr));
  181.                 stccpy(ce->ce_Type, "SEG_SINGLE", sizeof(ce->ce_Type));
  182.  
  183.                 AddTail((struct List *)&tmplist, (struct Node *)ce);
  184.              } else {
  185.                 LONG *_seg;
  186.                 BOOL first = TRUE;
  187.  
  188.                 _snprintf(ce->ce_UseCount, sizeof(ce->ce_UseCount), "%lD", seg->seg_UC - 1);
  189.  
  190.                 ce->ce_SegmentNum = 1;
  191.                 _snprintf(ce->ce_SegmentNumStr, sizeof(ce->ce_SegmentNumStr), "%lD", ce->ce_SegmentNum);
  192.  
  193.                 _seg = BADDR(seg->seg_Seg);
  194.                 do {
  195.                     if (_ce = AllocVec(sizeof(struct CommandEntry), MEMF_PUBLIC)) {
  196.                         LONG size;
  197.  
  198.                         CopyMem(ce, _ce, sizeof(struct CommandEntry));
  199.  
  200.                         size = *(_seg - 1);
  201.                         _snprintf(_ce->ce_Lower, sizeof(_ce->ce_Lower), "$%08lx", ((UBYTE *)_seg) + 4);
  202.                         _snprintf(_ce->ce_Size, sizeof(_ce->ce_Size), MUIX_R "%lD", size);
  203.                         _snprintf(_ce->ce_Upper, sizeof(_ce->ce_Upper), "$%08lx", ((UBYTE *)_seg) - 4 + size);
  204.  
  205.                         if (!first) {
  206.                             _ce->ce_SegmentNum++;
  207.                             _snprintf(_ce->ce_SegmentNumStr, sizeof(_ce->ce_SegmentNumStr), "%lD", _ce->ce_SegmentNum);
  208.                             stccpy(_ce->ce_Type, "SEG_NODE", sizeof(_ce->ce_Type));
  209.                         } else {
  210.                             stccpy(_ce->ce_Type, "SEG_LIST", sizeof(_ce->ce_Type));
  211.                             first = FALSE;
  212.                         }
  213.  
  214.                         AddTail((struct List *)&tmplist, (struct Node *)_ce);
  215.                     }
  216.  
  217.                     _seg = BADDR(*_seg);
  218.                 } while (_seg);
  219.              }
  220.         }
  221.  
  222.         seg = (struct Segment *)BADDR(seg->seg_Next);
  223.     }
  224.  
  225.     Permit();
  226.  
  227.     ITERATE_CHANGING_LIST(&tmplist, struct CommandEntry *, ce, _ce) {
  228.         callback(ce, userData);
  229.         FreeVec(ce);
  230.     }
  231. }
  232.  
  233. static void UpdateCallback( struct CommandEntry *ce,
  234.                             void *userData )
  235. {
  236.     struct CommandsCallbackUserData *ud = (struct CommandsCallbackUserData *)userData;
  237.     struct MUI_NListtree_TreeNode *parent;
  238.     ULONG flags;
  239.  
  240.     flags = 0;
  241.     if (stricmp(ce->ce_Type, "SEG_SINGLE") == 0) {
  242.         ud->ud_Count++;
  243.     } else if (stricmp(ce->ce_Type, "SEG_LIST") == 0) {
  244.         flags = TNF_LIST | TNF_OPEN | TNF_FROZEN;
  245.         ud->ud_Count++;
  246.     } else if (stricmp(ce->ce_Type, "SEG_NODE") == 0) {
  247.         // don't count up, this belongs to a SEG_LIST node
  248.     }
  249.  
  250.     parent = (struct MUI_NListtree_TreeNode *)DoMethod(ud->ud_Tree, MUIM_NListtree_FindUserData, MUIV_NListtree_FindUserData_ListNode_Root, ce->ce_Name, MUIV_NListtree_FindUserData_Flag_StartNode);
  251.     DoMethod(ud->ud_Tree, MUIM_NListtree_Insert, ce->ce_Name, ce, parent, MUIV_NListtree_Insert_PrevNode_Sorted, flags);
  252. }
  253.  
  254. static void PrintCallback( struct CommandEntry *ce,
  255.                            void *userData )
  256. {
  257.     if (ce->ce_SegmentNum == -1) {
  258.         PrintFOneLine((BPTR)userData, " %9s %-15.15s %8s %-9.9s %-9.9s %10.10s\n", ce->ce_Address, ce->ce_Name, ce->ce_UseCount, ce->ce_Lower + 2, ce->ce_Upper + 2, ce->ce_Size + 2);
  259.     } else if (ce->ce_SegmentNum == 1) {
  260.         PrintFOneLine((BPTR)userData, " %9s %-15.15s %8s %-9.9s %-9.9s %10.10s\n", ce->ce_Address, ce->ce_Name, ce->ce_UseCount, ce->ce_Lower, ce->ce_Upper, ce->ce_Size + 2);
  261.     } else {
  262.         PrintFOneLine((BPTR)userData, " %9s %-15.15s %8s %-9.9s %-9.9s %10.10s\n", "", "", "", ce->ce_Lower, ce->ce_Upper, ce->ce_Size + 2);
  263.     }
  264. }
  265.  
  266. static void SendCallback( struct CommandEntry *ce,
  267.                           void *userData )
  268. {
  269.     SendEncodedEntry((UBYTE *)ce, sizeof(struct CommandEntry));
  270. }
  271.  
  272. static ULONG __saveds mNew( struct IClass *cl,
  273.                             Object *obj,
  274.                             struct opSet *msg )
  275. {
  276.     APTR comlist, comtree, comtext, comcount, updateButton, printButton, removeButton, exitButton;
  277.  
  278.     if (obj = (Object *)DoSuperNew(cl, obj,
  279.         MUIA_HelpNode, CommandsText,
  280.         MUIA_Window_ID, MakeID('R','C','O','M'),
  281.         WindowContents, VGroup,
  282.  
  283.             Child, comlist = MyNListtreeObject(&comtree, "BAR,BAR,BAR,BAR,BAR,BAR,", &comtree_conhook, &comtree_deshook, &comtree_dsphook, &comtree_cmphook, &comtree_findhook, 3),
  284.             Child, MyBelowListview(&comtext, &comcount),
  285.  
  286.             Child, MyVSpace(4),
  287.  
  288.             Child, HGroup, MUIA_Group_SameSize, TRUE,
  289.                 Child, updateButton = MakeButton(txtUpdate),
  290.                 Child, printButton  = MakeButton(txtPrint),
  291.                 Child, removeButton = MakeButton(txtRemove),
  292.                 Child, exitButton   = MakeButton(txtExit),
  293.             End,
  294.         End,
  295.         TAG_MORE, msg->ops_AttrList))
  296.     {
  297.         struct CommandsWinData *cwd = INST_DATA(cl, obj);
  298.         APTR parent;
  299.  
  300.         cwd->cwd_CommandTree = comtree;
  301.         cwd->cwd_CommandText = comtext;
  302.         cwd->cwd_CommandCount = comcount;
  303.         cwd->cwd_RemoveButton = removeButton;
  304.  
  305.         parent = (APTR)GetTagData(MUIA_Window_ParentWindow, (ULONG)NULL, msg->ops_AttrList);
  306.  
  307.         set(obj, MUIA_Window_Title, MyGetWindowTitle("RESIDENT COMMANDS", cwd->cwd_Title, sizeof(cwd->cwd_Title)));
  308.         set(obj, MUIA_Window_ActiveObject, comlist);
  309.         set(removeButton, MUIA_Disabled, TRUE);
  310.  
  311.         DoMethod(parent,       MUIM_Window_AddChildWindow, obj);
  312.         DoMethod(obj,          MUIM_Notify, MUIA_Window_CloseRequest, TRUE,           MUIV_Notify_Application, 5, MUIM_Application_PushMethod, parent, 2, MUIM_Window_RemChildWindow, obj);
  313.         DoMethod(comtree,      MUIM_Notify, MUIA_NListtree_Active,    MUIV_EveryTime, obj,                     1, MUIM_CommandsWin_ListChange);
  314.         DoMethod(updateButton, MUIM_Notify, MUIA_Pressed,             FALSE,          obj,                     1, MUIM_CommandsWin_Update);
  315.         DoMethod(printButton,  MUIM_Notify, MUIA_Pressed,             FALSE,          obj,                     1, MUIM_CommandsWin_Print);
  316.         DoMethod(removeButton, MUIM_Notify, MUIA_Pressed,             FALSE,          obj,                     1, MUIM_CommandsWin_Remove);
  317.         DoMethod(exitButton,   MUIM_Notify, MUIA_Pressed,             FALSE,          obj,                     3, MUIM_Set, MUIA_Window_CloseRequest, TRUE);
  318.     }
  319.  
  320.     return (ULONG)obj;
  321. }
  322.  
  323. static ULONG __saveds mDispose( struct IClass *cl,
  324.                                 Object *obj,
  325.                                 struct opSet *msg )
  326. {
  327.     struct CommandsWinData *cwd = INST_DATA(cl, obj);
  328.  
  329.     set(obj, MUIA_Window_Open, FALSE);
  330.     DoMethod(cwd->cwd_CommandTree, MUIM_NListtree_Clear, NULL, 0);
  331.  
  332.     return (DoSuperMethodA(cl, obj, msg));
  333. }
  334.  
  335. static ULONG __saveds mUpdate( struct IClass *cl,
  336.                                Object *obj,
  337.                                Msg msg )
  338. {
  339.     struct CommandsWinData *cwd = INST_DATA(cl, obj);
  340.     struct CommandsCallbackUserData ud;
  341.  
  342.     ApplicationSleep(TRUE);
  343.     set(cwd->cwd_CommandTree, MUIA_NListtree_Quiet, TRUE);
  344.     DoMethod(cwd->cwd_CommandTree, MUIM_NListtree_Clear, NULL, 0);
  345.  
  346.     ud.ud_Tree = cwd->cwd_CommandTree;
  347.     ud.ud_Count = 0;
  348.  
  349.     if (clientstate) {
  350.         ReceiveList(UpdateCallback, &ud);
  351.     } else {
  352.         IterateList(UpdateCallback, &ud);
  353.     }
  354.  
  355.     SetCountText(cwd->cwd_CommandCount, ud.ud_Count);
  356.     MySetContents(cwd->cwd_CommandText, "");
  357.  
  358.     set(cwd->cwd_CommandTree, MUIA_NListtree_Quiet, FALSE);
  359.     set(cwd->cwd_RemoveButton, MUIA_Disabled, TRUE);
  360.     ApplicationSleep(FALSE);
  361.  
  362.     return 0;
  363. }
  364.  
  365. static ULONG __saveds mPrint( struct IClass *cl,
  366.                               Object *obj,
  367.                               Msg msg )
  368. {
  369.     PrintCommands(NULL);
  370.  
  371.     return 0;
  372. }
  373.  
  374. static ULONG __saveds mRemove( struct IClass *cl,
  375.                                Object *obj,
  376.                                Msg msg )
  377. {
  378.     struct CommandsWinData *cwd = INST_DATA(cl, obj);
  379.     struct MUI_NListtree_TreeNode *tn;
  380.  
  381.     if (tn = GetActiveTreeNode(cwd->cwd_CommandTree)) {
  382.         struct CommandEntry *ce = (struct CommandEntry *)tn->tn_User;
  383.  
  384.         if (ce->ce_UseCount[0] == 'I') {
  385.             MyRequest(msgErrorContinue, msgCantRemoveInternal);
  386.         } else if (ce->ce_UseCount[0] == 'S') {
  387.             MyRequest(msgErrorContinue, msgCantRemoveSystem);
  388.         } else if (ce->ce_UseCount[0] == 'D') {
  389.             MyRequest(msgErrorContinue, msgCantRemoveDisabled);
  390.         } else {
  391.             if (MyRequest(msgYesNo, msgWantToRemoveCommand, ce->ce_Name)) {
  392.                 MyDoCommand("RemoveCommand $%08lx", ce->ce_Addr);
  393.                 DoMethod(obj, MUIM_CommandsWin_Update);
  394.             }
  395.         }
  396.     }
  397.  
  398.     return 0;
  399. }
  400.  
  401. static ULONG __saveds mListChange( struct IClass *cl,
  402.                                    Object *obj,
  403.                                    Msg msg )
  404. {
  405.     struct CommandsWinData *cwd = INST_DATA(cl, obj);
  406.     struct MUI_NListtree_TreeNode *tn;
  407.  
  408.     if (tn = GetActiveTreeNode(cwd->cwd_CommandTree)) {
  409.         struct CommandEntry *ce = (struct CommandEntry *)tn->tn_User;
  410.  
  411.         MySetContents(cwd->cwd_CommandText, "%s \"%s\"", ce->ce_Address, ce->ce_Name);
  412.         set(cwd->cwd_RemoveButton, MUIA_Disabled, FALSE);
  413.     }
  414.  
  415.     return 0;
  416. }
  417.  
  418. ULONG __asm __saveds CommandsWinDispatcher( register __a0 struct IClass *cl,
  419.                                             register __a2 Object *obj,
  420.                                             register __a1 Msg msg )
  421. {
  422.     switch (msg->MethodID) {
  423.         case OM_NEW:                      return (mNew(cl, obj, (APTR)msg));
  424.         case OM_DISPOSE:                  return (mDispose(cl, obj, (APTR)msg));
  425.         case MUIM_CommandsWin_Update:     return (mUpdate(cl, obj, (APTR)msg));
  426.         case MUIM_CommandsWin_Print:      return (mPrint(cl, obj, (APTR)msg));
  427.         case MUIM_CommandsWin_Remove:     return (mRemove(cl, obj, (APTR)msg));
  428.         case MUIM_CommandsWin_ListChange: return (mListChange(cl, obj, (APTR)msg));
  429.     }
  430.  
  431.     return (DoSuperMethodA(cl, obj, msg));
  432. }
  433.  
  434. void PrintCommands( char *filename )
  435. {
  436.     BPTR handle;
  437.  
  438.     if (handle = HandlePrintStart(filename)) {
  439.         PrintFOneLine(handle, "\n  Address  Name            UseCount   Lower     Upper         Size\n\n");
  440.         IterateList(PrintCallback, (void *)handle);
  441.     }
  442.  
  443.     HandlePrintStop();
  444. }
  445.  
  446. void SendComList( void )
  447. {
  448.     IterateList(SendCallback, NULL);
  449. }
  450.  
  451.